﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using Autodesk.Revit.DB;
using Autodesk.Revit.UI;
using YArchitech.Revit;
using SystemDiagramNew.TypeDefinition;
using SystemDiagramNew.Utils;

namespace SystemDiagramNew
{
	public class VerticalPipeIsoDiagram
	{
		public VerticalPipeIsoDiagram(ExternalCommandData cmdData, ElementSet elements)
		{
			this.CommandData = cmdData;
			this.SelectedElements = elements.ToEnumerable();
			this.Name = "立管轴测图";
		}

		public bool Run()
		{
			this.DrawElements = this.GetElements();
			if (!this.DrawElements.Any<Element>())
			{
				this.ErrorMessage = "没有选中任何系统!";
				return false;
			}
			this.Name = this.GetName();
			ViewDrafting viewDrafting = this.CreateView();
			if (viewDrafting == null)
			{
				this.ErrorMessage = "创建视图失败 !";
				return false;
			}
			return this.Draw(viewDrafting, this.Name);
		}

		private string GetName()
		{
			Element elem2 = this.DrawElements.FirstOrDefault((Element elem) => elem is MEPCurve);
			string mark = elem2.GetMark();
			Parameter parameter = elem2.GetParameter(BuiltInParameter.RBS_DUCT_PIPE_SYSTEM_ABBREVIATION_PARAM);
			string str = (parameter == null) ? "" : parameter.AsString();
			return str + " " + mark;
		}

		public ExternalCommandData CommandData { get; set; }

		public IEnumerable<Element> SelectedElements { get; set; }

		public IEnumerable<Element> DrawElements { get; set; }

		public string Name { get; set; }

		public string ErrorMessage { get; set; }

		internal virtual IEnumerable<Element> GetElements()
		{
			if (this.SelectedElements != null && this.SelectedElements.Any<Element>())
			{
				return this.SelectedElements.Where(new Func<Element, bool>(VerticalPipeIsoDiagram.IsVertical));
			}
			VerticalElementFilter verticalElementFilter = new VerticalElementFilter();
			IList<Reference> list = this.CommandData.Application.ActiveUIDocument.Selection.PickObjects(Autodesk.Revit.UI.Selection.ObjectType.Element, verticalElementFilter, "请框选立管实体:");
			if (list == null || !list.Any<Reference>())
			{
				return Enumerable.Empty<Element>();
			}
			Document doc = this.CommandData.Application.ActiveUIDocument.Document;
			return from reference in list
			select doc.GetElementByRef(reference);
		}

		public static bool IsVertical(Element element)
		{
			if (!element.IsPipe() && !element.IsPipeAccessory() && !element.IsPipeFitting())
			{
				return false;
			}
			IEnumerable<Connector> connectors = element.GetConnectors();
			if (connectors == null || !connectors.Any<Connector>())
			{
				return false;
			}
			int num = connectors.Count<Connector>();
			if (num < 2 || num > 4)
			{
				return false;
			}
			Connector c = connectors.First<Connector>();
			Connector connector = connectors.ElementAtOrDefault(1);
			Connector c2 = connectors.ElementAtOrDefault(2);
			return VerticalPipeIsoDiagram.IsVertical(c, connector) || VerticalPipeIsoDiagram.IsVertical(c, c2) || VerticalPipeIsoDiagram.IsVertical(connector, c2);
		}

		public static bool IsVertical(XYZ p1, XYZ p2)
		{
			return !Geometry.IsEqual(p1.Z, p2.Z, VerticalPipeIsoDiagram.EqualDist) && Geometry.IsEqual(p1.X, p2.X, VerticalPipeIsoDiagram.EqualDist) && Geometry.IsEqual(p1.Y, p2.Y, VerticalPipeIsoDiagram.EqualDist);
		}

		public static bool IsVertical(Connector c1, Connector c2)
		{
			return c1 != null && c2 != null && VerticalPipeIsoDiagram.IsVertical(c1.Origin, c2.Origin);
		}

		private SelectedElement GetFirstElement()
		{
			return this.CommandData.Application.ActiveUIDocument.PickMEPCurve("选择一根管道");
		}

		private string BuildViewName()
		{
			return string.Format("{0}  {1}", this.Name, "立管轴测图");
		}

		private ViewDrafting CreateView()
		{
			string text = this.BuildViewName();
			ViewDrafting viewDrafting = this.CommandData.GetDocument().CreateNewViewDrafting(ref text, 100);
			if (viewDrafting == null)
			{
				this.ErrorMessage = "创建视图失败!";
				return null;
			}
			this.CommandData.Application.ActiveUIDocument.SetActiveView(viewDrafting);
			return viewDrafting;
		}

		private bool Draw(ViewDrafting drawView, string viewTitle)
		{
			IntPtr mainWindowHandle = Process.GetCurrentProcess().MainWindowHandle;
			LoadingForm loadingForm = new LoadingForm();
			loadingForm.Show(mainWindowHandle);
			this.DrawDiagram2(drawView, viewTitle);
			loadingForm.Close();
			return true;
		}

		public bool DrawDiagram3(ViewDrafting drawView, string viewName)
		{
			using (Transaction transaction = new Transaction(this.CommandData.Application.ActiveUIDocument.Document, "DrawVerticalDiagram"))
			{
				IEnumerable<ElementId> source = from elem in this.DrawElements
				select elem.Id;
				transaction.Start();
				drawView.UnhideElements(source.ToList<ElementId>());
				this.CommandData.UpdateModel(true);
				transaction.Commit();
				UIView uiview = this.CommandData.Application.ActiveUIDocument.GetOpenUIViews().FirstOrDefault((UIView v) => v.ViewId == drawView.Id);
				if (uiview != null)
				{
					uiview.ZoomToFit();
				}
			}
			return true;
		}

		public bool DrawDiagram2(ViewDrafting drawView, string viewName)
		{
			double num = 45.0;
			double xScale = 1.0;
			double yScale = 1.0;
			double zScale = 1.0;
			double legendScale = 1.0;
			SystemDiagramAnalyser systemDiagramAnalyser = new SystemDiagramAnalyser(this.CommandData);
			PipingSystemInfo pipingSystemInfo = systemDiagramAnalyser.Analyse(viewName, this.DrawElements, num, xScale, yScale, zScale);
			Result result = Result.Failed;
			using (Transaction transaction = new Transaction(this.CommandData.Application.ActiveUIDocument.Document, "DrawVerticalDiagram"))
			{
				transaction.Start();
				result = new DrawingKit(this.CommandData, num, legendScale)
				{
					View = drawView,
					IsVertical = true
				}.Drawing(pipingSystemInfo, true, true);
				this.CommandData.UpdateModel(true);
				transaction.Commit();
				UIView uiview = this.CommandData.Application.ActiveUIDocument.GetOpenUIViews().FirstOrDefault((UIView v) => v.ViewId == drawView.Id);
				if (uiview != null)
				{
					uiview.ZoomToFit();
				}
			}
			return 0 == result;
		}

		private const string NameTail = "立管轴测图";

		public static double EqualDist = 1E-05;
	}
}
